home *** CD-ROM | disk | FTP | other *** search
/ Sprite 1984 - 1993 / Sprite 1984 - 1993.iso / src / kernel / dev / sun4.md / devInit.c < prev    next >
C/C++ Source or Header  |  1992-12-18  |  8KB  |  263 lines

  1. /*
  2.  * devInit.c --
  3.  *
  4.  *    This has a weak form of autoconfiguration for mapping in various
  5.  *    devices and calling their initialization routines.  The file
  6.  *    devConfig.c has the tables which list devices, their physical
  7.  *    addresses, and their initialization routines.
  8.  *
  9.  *    The Sun Memory Managment setup is explained in the proprietary
  10.  *    architecture documents, and also in the manual entitled
  11.  *    "Writing Device Drivers for the Sun Workstation"
  12.  *
  13.  *
  14.  * Copyright 1985, 1989 Regents of the University of California
  15.  * Permission to use, copy, modify, and distribute this
  16.  * software and its documentation for any purpose and without
  17.  * fee is hereby granted, provided that the above copyright
  18.  * notice appear in all copies.  The University of California
  19.  * makes no representations about the suitability of this
  20.  * software for any purpose.  It is provided "as is" without
  21.  * express or implied warranty.
  22.  */
  23.  
  24. #ifndef lint
  25. static char rcsid[] = "$Header: /cdrom/src/kernel/Cvsroot/kernel/dev/sun4.md/devInit.c,v 9.5 91/10/18 01:21:43 dlong Exp $ SPRITE (Berkeley)";
  26. #endif not lint
  27.  
  28. #include "sprite.h"
  29. #include "stdio.h"
  30. #include "devInt.h"
  31. #include "devMultibus.h"
  32. #include "vm.h"
  33. #include "vmMach.h"
  34. #include "dbg.h"
  35. #include "string.h"
  36. #include "ttyAttach.h"
  37. #ifdef sun4c
  38. #include "machMon.h"
  39. #endif
  40.  
  41. int devConfigDebug = FALSE;
  42.  
  43. /*
  44.  * ----------------------------------------------------------------------------
  45.  *
  46.  * Dev_Init --
  47.  *
  48.  *    Device initialization.
  49.  *
  50.  * Results:
  51.  *    None
  52.  *
  53.  * Side effects:
  54.  *    Set up interrupt routine for built-in UART interrupts.
  55.  *
  56.  * ----------------------------------------------------------------------------
  57.  */
  58.  
  59. void
  60. Dev_Init()
  61. {
  62.     DevTtyInit();
  63. }
  64.  
  65.  
  66. /*
  67.  *----------------------------------------------------------------------
  68.  *
  69.  * Dev_Config --
  70.  *
  71.  *    Call the initialization routines for various controllers and
  72.  *    devices based on configuration tables.  This should be called
  73.  *    after the regular memory allocater is set up so the drivers
  74.  *    can use it to configure themselves.
  75.  *
  76.  * Results:
  77.  *    None.
  78.  *
  79.  * Side effects:
  80.  *    Call the controller and device initialization routines.
  81.  *
  82.  *----------------------------------------------------------------------
  83.  */
  84. void
  85. Dev_Config()
  86. {
  87.     register int index;
  88.     int memoryType = 0;        /* This is ultimatly for the page table
  89.                  * type field used to map in the device */
  90.     Boolean mapItIn = FALSE;    /* If TRUE we need to map the device into
  91.                  * kernel virtual space */
  92.  
  93.     if (devConfigDebug) {
  94.     printf("Dev_Config calling debugger:");
  95.     DBG_CALL;
  96.     }
  97.     for (index = 0 ; index < devNumConfigCntrlrs ; index++) {
  98.     register DevConfigController *cntrlrPtr;
  99.     cntrlrPtr = &devCntrlr[index];
  100.     /*
  101.      * The following makes sure that the physical address for the
  102.      * controller is correct, and then maps that into the kernel's virtual
  103.      * address space (if it hasn't already been done by the Boot PROM).
  104.      * There are two things happening here.  First, each device has
  105.      * its own physical address on its own kind of bus - A device may
  106.      * think it's in Multibus Memory, or VME bus 16 bit data 16 bit address,
  107.      * or some other permutation.  For Multibus Memory devices, like
  108.      * the SCSI controller, Multibus memory is the low megabyte of
  109.      * the physical addresses, with Multibus I/O being the last 64K
  110.      * of this first Meg.  Furthermore, the Boot PROM maps this low
  111.      * meg of physical memory into the 16'th Meg of the kernel's virtual
  112.      * address space.  All that needs to be done is imitate this mapping
  113.      * by adding the MULTIBUS BASE to the controller address and the
  114.      * controller can forge ahead.
  115.      * It's more complicated for VME devices.  There are six subsets
  116.      * of address/data spaces supported by the VME bus, and each one
  117.      * belongs to a special range of physical addresses and has a
  118.      * corresponding "page type" which goes into the page table.
  119.      * Furthermore, we arn't depending on the boot PROM and so once
  120.      * the correct physical address is gen'ed up we need to map it
  121.      * into a kernel virtual address that the device driver can use.
  122.      */
  123. #ifdef sun4c
  124.     if (Mach_MonSearchProm(cntrlrPtr->dev_name, "address",
  125.         (char *)cntrlrPtr->address,
  126.         sizeof cntrlrPtr->address) == sizeof cntrlrPtr->address) {
  127.         mapItIn = FALSE;
  128.     } else {
  129.         MachDevReg reg;
  130.         if (Mach_MonSearchProm(cntrlrPtr->dev_name, "reg",
  131.             (char *)®, sizeof reg) == sizeof reg) {
  132.         mapItIn = TRUE;
  133.         memoryType = 1;
  134.         if (romVectorPtr->v_romvec_version < 2
  135.             && reg.addr >= (Address)SBUS_BASE
  136.             && reg.bustype == 1) {        /* old style */
  137.             cntrlrPtr->address = (int)reg.addr;
  138.         } else {                /* new style */
  139.             cntrlrPtr->address = (int)reg.addr + SBUS_BASE +
  140.                reg.bustype * SBUS_SIZE;
  141.         }
  142.         }
  143.     }
  144. #else
  145.     if (Mach_GetMachineType() == SYS_SUN_2_120 &&
  146.         cntrlrPtr->space != DEV_MULTIBUS &&
  147.         cntrlrPtr->space != DEV_MULTIBUS_IO) {
  148.         /*
  149.          * Mapping VME addresses into a multibus based kernel
  150.          * messes things up.
  151.          */
  152.         continue;
  153.     }
  154.     switch(cntrlrPtr->space) {
  155.         case DEV_MULTIBUS:
  156.         case DEV_MULTIBUS_IO:
  157.         /*
  158.          * Things are already mapped in by the Boot PROM.
  159.          * We just relocate the address into the high meg.
  160.          */
  161.         if (Mach_GetMachineType() != SYS_SUN_2_120) {
  162.             continue;
  163.         }
  164.         mapItIn = FALSE;
  165.         cntrlrPtr->address += DEV_MULTIBUS_BASE;
  166.         break;
  167.         /*
  168.          * We have to relocate the controller address to the
  169.          * true VME PHYSICAL address that the Sun MMU uses for
  170.          * the different types of VME spaces.
  171.          */
  172.         case DEV_VME_D32A16:
  173.         case DEV_VME_D16A16:
  174.         /*
  175.          * The high 64K of the VME address range is stolen for the
  176.          * 16 bit address subset.
  177.          */
  178.         mapItIn = TRUE;
  179.         cntrlrPtr->address += 0xFFFF0000;
  180.         break;
  181.         case DEV_VME_D32A24:
  182.         case DEV_VME_D16A24:
  183.         /*
  184.          * The high 16 Megabytes of the VME address range is stolen
  185.          * for the 24 bit address subset.
  186.          */
  187.         mapItIn = TRUE;
  188.         cntrlrPtr->address += 0xFF000000;
  189.         break;
  190.         /*
  191.          * The addresses for the full 32 bit VME bus are ok.
  192.          */
  193.         case DEV_VME_D16A32:
  194.         case DEV_VME_D32A32:
  195.         mapItIn = TRUE;
  196.         break;
  197.         case DEV_OBIO:
  198.         mapItIn = FALSE;
  199.         break;
  200.     }
  201.     /*
  202.      * Each different Sun architecture arranges pieces of memory into
  203.      * 4 different spaces.  The I/O devices fall into type 2 or 3 space.
  204.      */
  205.     switch(cntrlrPtr->space) {
  206.         case DEV_MULTIBUS:
  207.         memoryType = 2;
  208.         break;
  209.         case DEV_VME_D16A16:
  210.         case DEV_VME_D16A24:
  211.         case DEV_VME_D16A32:
  212.         if (Mach_GetMachineType() == SYS_SUN_2_50) {
  213.             if (cntrlrPtr->address >= 0xFF800000) {
  214.             memoryType = 3;
  215.             } else {
  216.             memoryType = 2;
  217.             }
  218.         } else {
  219.             memoryType = 2;
  220.         }
  221.         break;
  222.         case DEV_MULTIBUS_IO:
  223.         case DEV_VME_D32A16:
  224.         case DEV_VME_D32A24:
  225.         case DEV_VME_D32A32:
  226.         memoryType = 3;
  227.         break;
  228.         case DEV_OBIO:
  229.         memoryType = 1;
  230.         break;
  231.     }
  232. #endif
  233.     if (mapItIn) {
  234.         if (devConfigDebug) {
  235.         printf("Dev config mapping %s at 0x%x, memType %d.\n",
  236.             cntrlrPtr->name, cntrlrPtr->address, memoryType);
  237.         }
  238.         cntrlrPtr->address =
  239.             (int) VmMach_MapInDevice((Address) cntrlrPtr->address,
  240.             memoryType);
  241.         if (devConfigDebug) { printf("Dev config virtual addr is 0x%x.\n",
  242.             cntrlrPtr->address);
  243.         }
  244.     }
  245.     if (cntrlrPtr->address != NIL) {
  246.         ClientData    callBackData;
  247.  
  248.         if (cntrlrPtr->initProc != (ClientData (*)()) NIL) {
  249.         callBackData = (*cntrlrPtr->initProc)(cntrlrPtr);
  250.         if (callBackData != DEV_NO_CONTROLLER) {
  251.             printf("%s at kernel address %x\n", cntrlrPtr->name,
  252.                    cntrlrPtr->address);
  253.             if (cntrlrPtr->vectorNumber > 0) {
  254.             Mach_SetHandler(cntrlrPtr->vectorNumber,
  255.                 cntrlrPtr->intrProc, callBackData);
  256.             }
  257.         }
  258.         }
  259.     }
  260.     }
  261.     return;
  262. }
  263.